package com.itic.appbase.applications.sys.common.service.impl;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.HashMap;
import java.util.Iterator;
import java.util.List;
import java.util.Map;

import org.apache.commons.lang3.StringUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;

import com.itic.appbase.applications.cacheutils.CodeCache;
import com.itic.appbase.applications.files.persistence.model.Files;
import com.itic.appbase.applications.files.service.FilesService;
import com.itic.appbase.applications.sys.code.persistence.dao.CodeDetailDao;
import com.itic.appbase.applications.sys.code.persistence.model.CodeDetail;
import com.itic.appbase.applications.sys.code.persistence.model.CodeDetailExample;
import com.itic.appbase.applications.sys.code.persistence.model.CodeDetailExample.Criteria;
import com.itic.appbase.applications.sys.code.vo.CodeDetailVo;
import com.itic.appbase.applications.sys.common.persistence.dao.OutCommonDao;
import com.itic.appbase.applications.sys.common.service.OutCommonService;
import com.itic.appbase.applications.sys.org.persistence.dao.OrgDao;
import com.itic.appbase.applications.sys.org.persistence.model.Org;
import com.itic.appbase.applications.sys.region.persistence.dao.RegionDao;
import com.itic.appbase.applications.sys.region.persistence.model.Region;
import com.itic.appbase.applications.sys.region.persistence.model.RegionExample;
import com.itic.appbase.applications.sys.user.persistence.dao.SysUserDao;
import com.itic.appbase.applications.sys.user.persistence.model.SysUser;
import com.itic.appbase.framework.common.constants.DBConst;
import com.itic.appbase.framework.utils.PropertyGetter;
import com.itic.appbase.framework.utils.ReflectHelper;
import com.itic.appbase.framework.utils.StringHelper;
import com.itic.appbase.framework.utils.configuration.PropertyHelper;

/**
 * 对外提供接口实现类
 * <p>Company: itic</p>
 * 
 * @author: shijun
 * @date: 2015年6月12日 下午3:48:11
 * @version: V1.0
 */
@Service(value = "outCommonService")
public class OutCommonServiceImpl
        implements OutCommonService {

    @Autowired
    private CodeDetailDao codeDetailDao;
    @Autowired
    private OrgDao orgDao;
    @Autowired
    private RegionDao regionDao;
    @Autowired
    private SysUserDao sysUserDao;
    @Autowired
    private OutCommonDao outCommonDao;
    @Autowired
    private FilesService filesService;
    
    
    private static final String IS_EFFECTIVE = "isEffective";

    /**
     * 查询代码详情表集合
     * 
     * @param codeDetailVo
     *            封装type和filter
     * @return List：CodeDetail
     */
    @Override
    public List<CodeDetail> getCodeDetail(CodeDetailVo codeDetailVo) {
        List<CodeDetail> codeList = new ArrayList<CodeDetail>();
        if (null != codeDetailVo && StringHelper.isNotBlank(codeDetailVo.getType())) {
            // 根据代码表类型，获取缓存中的代码表信息
            codeList = CodeCache.get(codeDetailVo.getType());
            if (null == codeList || codeList.isEmpty()) {
                CodeDetailExample detailExample = new CodeDetailExample();
                detailExample.setOrderByClause("ORDER_NO asc");
                Criteria criteria = detailExample.createCriteria().andIsEffectiveEqualTo(DBConst.TRUE);
                criteria.andTypeEqualTo(codeDetailVo.getType());
                codeList = codeDetailDao.selectByExample(detailExample);
                // 将相应类型的代码表信息，添加到缓存
                CodeCache.put(codeDetailVo.getType(), codeList);
            }
            // 过滤不需要的代码表,返回过滤后的代码集合
            if (StringHelper.isNotBlank(codeDetailVo.getFilterCode())) {
                List<CodeDetail> filteredCode = new ArrayList<CodeDetail>();
                String[] filterCode = codeDetailVo.getFilterCode().trim().split(",");
                Arrays.sort(filterCode);
                String code = "";
                for (CodeDetail codeDetail : codeList) {
                    code = codeDetail.getCode();
                    if (StringHelper.isNotBlank(code) && Arrays.binarySearch(filterCode, code) < 0) {
                        filteredCode.add(codeDetail);
                    }
                }
                codeList.clear();
                return filteredCode;
            }
        }
        return codeList;
    }

    /**
     * 根据代码获取名称
     * 
     * @param obj 对象
     * @param codeMap {map.put('type', 't_dm_xx')}
     * @return
     */
    @Override
    public Object getNameByCode(Object obj, Map<String, String> codeMap) {
        if (null != codeMap && !codeMap.isEmpty()) {
            Iterator<String> codeIterator = codeMap.keySet().iterator();
            List<CodeDetail> codeDetailList = new ArrayList<CodeDetail>();
            CodeDetailVo codeDetailVo = new CodeDetailVo();
            while (codeIterator.hasNext()) {
                // 获取key
                String type = codeIterator.next();
                codeDetailVo.setType(codeMap.get(type));
                codeDetailList = this.getCodeDetail(codeDetailVo);
                // 获取key对应obj中的code值
                String codeValue = (String) ReflectHelper.getValueByFieldName(obj, type);
                // 获取code对应的代码名称
                if (StringHelper.isNotBlank(codeValue)) {
                    for (CodeDetail codeDetail : codeDetailList) {
                        if (codeValue.equals(codeDetail.getCode())) {
                            ReflectHelper.setValueByFieldName(obj, type, codeDetail.getName());
                            break;
                        }
                    }
                }
            }

        }
        return obj;
    }

    /**
     * 根据org(code/pCode/clazz)获取组织机构树
     * 
     * @param queryOrg
     * @return List
     */
    @Override
    public List<Org> getOrgTree(Org queryOrg) {
        // code不为null时，以code查询，pCode置空
        if (null != queryOrg && StringHelper.isNotBlank(queryOrg.getCode())) {
            queryOrg.setpCode(null);
        }
        return orgDao.selectOrgTree(queryOrg);
    }

    /**
     * 根据组织机构code获取组织机构对象
     * 
     * @param code
     * @return Org
     */
    @Override
    public Org getOrgByCode(String code) {
        Org org = null;
        if (StringHelper.isNotBlank(code)) {
            Org orgTemp = new Org();
            orgTemp.setIsEffective(DBConst.TRUE);
            orgTemp.setCode(code);
            org = orgDao.selectOrgByCode(orgTemp);
        }
        return org;
    }
    
    /**
     *  根据组织机构code获取组织机构名称
     * @param code
     * @return
     */
    @Override
    public String getOrgNameByCode(String code) {
        Org org = this.getOrgByCode(code);
        return (null != org && StringHelper.isNotBlank(org.getName())) ? org.getName() : "";
    }

    /**
     * 获取行政区划树
     * 
     * @param region
     * @return List
     */
    @Override
    public List<Region> getRegionTree(Region region) {
        // id不为null时，以id查询，pId置空
        if (null != region && StringHelper.isNotBlank(region.getId())) {
            region.setpId(null);
        }
        String isMysql = PropertyGetter.getString("app.db.type");
        if( StringHelper.isNotBlank(isMysql)&&"mysql".equals(isMysql) ){
    		RegionExample example = new RegionExample();
    		com.itic.appbase.applications.sys.region.persistence.model.RegionExample.Criteria criteria = example.createCriteria();
    		criteria.andIsEffectiveEqualTo(DBConst.TRUE);
    		if(StringHelper.isNotBlank(region.getId())){
        		criteria.andPIdEqualTo(region.getId());
    		}
    		return regionDao.selectByExample(example);
    	}else{
    		return regionDao.selectRegionList(region);
    	}
        //return regionDao.selectRegionList(region);
    }
    
    /**
     * 获取行政区划树（灾情现场资料）
     * 
     * @param region
     * @return List
     */
    @Override
    public List<Region> selectRegionListForZqxczl(Region region) {
        return regionDao.selectRegionListForZqxczl(region);
    }

    /**
     * 根据行政区划id获取行政区划
     * 
     * @param id
     * @return Region
     */
    @Override
    public Region getRegionById(String id) {
        if (StringHelper.isNotBlank(id)) {
            return regionDao.selectByPrimaryKey(id);
        }
        return null;
    }
    
    /**
     * 根据id获取行政区划名称
     * 
     * @param id
     * @return
     */
    @Override
    public String getRegionNameById(String id) {
        Region region = regionDao.selectByPrimaryKey(id);
        return (null != region && StringHelper.isNotBlank(region.getName())) ? region.getName() : "";
    }

    /**
     * 根据行政区划code获取行政区划
     * 
     * @param code
     * @return Region
     */
    @Override
    public Region getRegionByCode(String code) {
        if (StringHelper.isNotBlank(code)) {
            RegionExample regionExample = new RegionExample();
            regionExample.createCriteria().andIsEffectiveEqualTo(DBConst.TRUE).andCodeEqualTo(code);
            List<Region> regionList = regionDao.selectByExample(regionExample);
            if (null != regionList && !regionList.isEmpty()) {
                return regionList.get(0);
            }
        }
        return null;
    }
    
    /**
     * 权限过滤：根据传入的行政区划id获取本级和所有上级行政区划对象
     * 
     * @param regionId 行政区划id
     * @return
     */
    @Override
    public List<Region> getSjAllRegionByRegionId(String regionId) {
        List<Region> list = new ArrayList<Region>();
        if (StringHelper.isNotBlank(regionId)) {
            Map<String, Object> param = new HashMap<String, Object>();
            param.put(IS_EFFECTIVE, DBConst.TRUE);
            param.put("id", regionId);
            list = regionDao.getSjAllRegionByRegionId(param);
        } 
        return list;
    }
    
    /**
     * 根据行政区划码code获取行政区划名称
     * 
     * @param code
     * @return
     */
    @Override
    public String getRegionNameByCode(String code) {
        Region region = this.getRegionByCode(code);
        return (null != region && StringHelper.isNotBlank(region.getName())) ? region.getName() : "";
    }

    /**
     * 根据用户id获取用户
     * 
     * @param id
     * @return SysUser
     */
    @Override
    public SysUser getUserById(String id) {
        if (StringHelper.isNotBlank(id)) {
            return sysUserDao.selectByPrimaryKey(id);
        }
        return null;
    }
    
    /**
     * 根据用户id获取组织机构
     */
    @Override
    public Org getOrgByUserId(String userId) {
        if (StringHelper.isBlank(userId)) {
            return null;
        } else {
            SysUser user = this.getUserById(userId);
            return this.getOrgByCode(user.getOrg());
        }
    }

    /**
     * 权限过滤：根据组织机构码获取本下级code list
     * @param orgCode 组织机构码
     * @return
     */
    @Override
    public List<String> getBxjOrgByCode(String orgCode) {
        List<String> list = new ArrayList<String>();
        if (StringHelper.isNotBlank(orgCode)) {
            Map<String, Object> param = new HashMap<String, Object>();
            param.put(IS_EFFECTIVE, DBConst.TRUE);
            param.put("code", orgCode);
            list = outCommonDao.getOrgByOrgCode(param);
        } 
        return list;
    }

    /**
     * 权限过滤：根据组织机构码获取下级code list
     * @param orgCode 组织机构码
     * @return
     */
    public List<String> getXjOrgByCode(String orgCode) {
        List<String> list = new ArrayList<String>();
        if (StringHelper.isNotBlank(orgCode)) {
            Map<String, Object> param = new HashMap<String, Object>();
            param.put(IS_EFFECTIVE, DBConst.TRUE);
            param.put("pCode", orgCode);
            list = outCommonDao.getOrgByOrgCode(param);
        } 
        return list;
    }

    /**
     * 权限过滤：根据行政区划id获取本下级code list
     * @param regionId 行政区划id
     * @return
     */
    @Override
    public List<String> getBxjOrgByRegionId(String regionId) {
        List<String> list = new ArrayList<String>();
        if (StringHelper.isNotBlank(regionId)) {
            Map<String, Object> param = new HashMap<String, Object>();
            param.put(IS_EFFECTIVE, DBConst.TRUE);
            param.put("id", regionId);
            list = outCommonDao.getOrgByRegionId(param);
        } 
        return list;
    }

    /**
     * 权限过滤：根据行政区划id获取下级code list
     * @param regionId 行政区划id
     * @return
     */
    @Override
    public List<String> getXjOrgByRegionId(String regionId) {
        List<String> list = new ArrayList<String>();
        if (StringHelper.isNotBlank(regionId)) {
            Map<String, Object> param = new HashMap<String, Object>();
            param.put(IS_EFFECTIVE, DBConst.TRUE);
            param.put("pId", regionId);
            list = outCommonDao.getOrgByRegionId(param);
        } 
        return list;
    }

    /**
	 * 获取当前登录人的本下级行政区划树---包括村级
	 * 
	 * @param regionId 行政区划id
	 * @return
	 */
	public List<Region> getRegionTreeCj(Region region){
		return outCommonDao.getRegionTreeCj(region);
	}
	
	@Override
    public String getNameByCode(String type, String code) {
        String name = "";
        if (StringUtils.isNotBlank(type) && StringUtils.isNotBlank(code)){
            CodeDetailExample detailExample = new CodeDetailExample();
            detailExample.createCriteria().andTypeEqualTo(type).andCodeEqualTo(code).andIsEffectiveEqualTo(DBConst.TRUE);
            List<CodeDetail> codeDetails = codeDetailDao.selectByExample(detailExample);
            name =  (null != codeDetails && !codeDetails.isEmpty())? codeDetails.get(0).getName() : "";
        } 
        return name;
    }

	 /**
     * 批量删除附件
     * @param ids
     * @return String
     */
	@Override
	public String deleteFiles(String ids) {
		return filesService.delFiles(ids);
	}

	/**
     * 根据fileId获取fileUrl路径
     */
	@Override
	public String getFileUrl(String fileId) {
		String result = "file_not_find";
		Files files = filesService.get(fileId);
		if( null != files ){
			String filePath = files.getFilePath();
			String downloadStr = PropertyHelper.getString("app.download.path");
			if( StringHelper.isNotBlank(downloadStr) ){
				String projectName = PropertyHelper.getString("app.code");
	            StringBuilder rootDir = new StringBuilder();
	            rootDir.append(downloadStr).append("/")
	                   .append(projectName == null ? "" : (projectName+"_"))
	                   .append("fileupload").append("/");
				result = rootDir.toString()+filePath;
			}else{
				//再完善
				result = "..." + filePath;
			}
		}
		return result;
	}

	@Override
	public String getFilePath(String fileId) {
		return filesService.get(fileId).getFilePath();
	}
}
